/**
 * @FileName			MessageDaoImp.java
 * @Author				BOCAI
 * @Version				V1.0
 * @CreateTime		2017年4月22日		下午7:16:06
 * @Copyright			Copyright(C) 2016-2017 All rights Reserved, Designed By BOCAI
 */
package com.like.system.message;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.ArrayList;
import java.util.List;

import org.apache.commons.beanutils.BeanUtils;
import org.apache.log4j.Logger;

import com.like.common.ResultType;
import com.like.common.jdbc.DaoSupport;
import com.like.common.util.StringUtils;
import com.like.system.user.User;


/**
 * @ClassName			MessageDaoImp
 * @Description			消息的数据持久控制器
 * @Author					BOCAI
 * @CreateTime			2017年4月22日		下午7:16:06
 * @Version					V1.0
 * @History
 * Date         Author        Version        Discription
 * ---------------------------------------------------------------------------
 * 2017年4月22日     	BOCAI      	1.0             1.0
 * 
 * Why & What is modified:
 * 
 */
public class MessageDaoImp extends DaoSupport implements MessageDao {
	
	public MessageDaoImp(){
		this.logger = Logger.getLogger(MessageDaoImp.class);
	}

	@Override
	public int add(Message message) throws Exception {
		int result = ResultType.FAIL;
		
		try{
			this.setConnection(true);
			String sql = MessageArgument.INSERT_SQL ;
			statement = this.connection.prepareStatement(sql);
			List<String> list = StringUtils.getFieldBySql(sql);
			int location = 1;
			
			for(String field : list){
				statement.setString(location, BeanUtils.getProperty(message, field));
				location++;		
			}	
			
			result = statement.executeUpdate();
			
		}catch(Exception e){
			this.logger.error(e);
			throw e ;
			
		}finally{
			this.dispose(this.connection, this.statement, this.set);
			
		}
		
		return result;
	}

	@Override
	public int delete(Message message) throws Exception {
		int result = ResultType.FAIL;
		
		try{
			this.setConnection(false);
			String sql = MessageArgument.DELETE_SQL;
			statement = this.connection.prepareStatement(sql);
			statement.setString(1, BeanUtils.getProperty(message, "mid"));
			result = statement.executeUpdate();
			
			if( result != 0){
				sql = MessageArgument.DELETE_SQL2;
				sql = sql.replace("{0}", message.getMid());
				statement.executeUpdate(sql);
			}
			
			this.connection.commit();
			
		}catch(Exception e){
			this.connection.rollback();
			this.logger.error(e);
			throw e ;
			
		}finally{
			this.dispose(this.connection, this.statement, this.set);
			
		}
		
		return result;
	}

	@Override
	public int update(Message message) throws Exception {
		int result = ResultType.FAIL;
		
		try{
			this.setConnection(true);
			String sql = MessageArgument.UPDATE_SQL;
			String[] Strings =  this.setWhere(message,1);
			sql = sql + Strings[2];
			statement = this.connection.prepareStatement(sql);
			
			if(Strings[1].length() != 0){
				Strings = Strings[1].split(",");
				int location = 1;
				
				for(String field : Strings){
					statement.setString(location, BeanUtils.getProperty(message, field));
					location++;
				}
				
			}
			
			result = statement.executeUpdate();
			
		}catch(Exception e){
			this.logger.error(e);
			throw e ;
			
		}finally{
			this.dispose(this.connection, this.statement, this.set);
			
		}
		
		return result;
	}

	@Override
	public List<Message> list(Message message) throws Exception {
		return this.list(message, 0, -1);
	}

	@Override
	public List<Message> list(Message message, int start, int count) throws Exception {
		return this.list(message, start, count, "message.mdatetime");
	}

	@Override
	public List<Message> list(Message message, int start, int count, String orderBy) throws Exception {
		List<Message> result = new ArrayList<Message>();
		
		try{
			this.setConnection(true);
			int rowCount = this.size(message,this.connection);
			String sql = MessageArgument.QUERY_SQL;
			String[] Strings =  this.setWhere(message,0);
			sql = sql + Strings[0];
			
			if( orderBy != null && !orderBy.equals("") ){
				sql = sql + " order by " + orderBy + " DESC";
			}
			
			if( count > 0 ){
				
				if( ( start + count ) >= rowCount ){
					count = count - ( start + count - rowCount );
				}
				
				sql = sql + " limit " + start +  "," + count;
			}
			
			this.statement = this.connection.prepareStatement(sql);
			
			if(Strings[1].length() != 0){
				Strings = Strings[1].split(",");
				int location = 1;
				
				for(String field : Strings){
					statement.setString(location, BeanUtils.getProperty(message, field));
					location++;
				}

			}
			
			this.set = this.statement.executeQuery();
			
			while( this.set.next() ){
				Message obj = new Message();
				User user = new User();
				BeanUtils.setProperty(obj, "mid", this.set.getString("mid"));
				BeanUtils.setProperty(obj, "mcontent", this.set.getString("mcontent"));
				BeanUtils.setProperty(obj, "mdatetime", this.set.getString("mdatetime").substring(0, 19));
				BeanUtils.setProperty(user, "uid", this.set.getString("uid"));
				BeanUtils.setProperty(user, "ualais", this.set.getString("ualais"));
				BeanUtils.setProperty(user, "uimage", this.set.getString("uimage"));
				BeanUtils.setProperty(obj, "user", user);
				result.add(obj);
			}
			
		}catch(Exception e ){
			this.logger.error(e);
			throw e;
			
		}finally{
			this.dispose(connection, statement, set);
			
		}
		
		return result;
	}

	@Override
	public int size(Message message) throws Exception {
		int rowCount = 0 ;
		
		try{
			this.setConnection(true);
			rowCount = this.size(message, connection);
			
		}catch(Exception e ){
			this.logger.error(e);
			throw e;
			
		}finally{
			this.dispose(connection, statement, set);
			
		}
		
		return rowCount ;
	}

	@Override
	public Message get(String id) throws Exception {
		Message result = null ;
		
		try{
			this.setConnection(true);
			String sql = MessageArgument.QUERY_SQL ;
			sql = sql + " and mid=? ";
			this.statement = this.connection.prepareStatement(sql);
			this.statement.setString(1, id);
			this.set = this.statement.executeQuery();
			result = new Message() ;
			
			if( this.set.next() ){
				User user = new User();
				BeanUtils.setProperty(result, "mid", this.set.getString("mid"));
				BeanUtils.setProperty(result, "mcontent", this.set.getString("mcontent"));
				BeanUtils.setProperty(result, "mdatetime", this.set.getString("mdatetime").substring(0, 19));
				BeanUtils.setProperty(user, "uid", this.set.getString("uid"));
				BeanUtils.setProperty(user, "ualais", this.set.getString("ualais"));
				BeanUtils.setProperty(user, "uimage", this.set.getString("uimage"));
				BeanUtils.setProperty(result, "user", user);
			}
			
		}catch(Exception e ){
			this.logger.error(e);
			throw e;
			
		}finally{
			this.dispose(connection, statement, set);
			
		}
		
		return result ;
	}

	/**
	 * 
	 * @Description				根据过滤条件获取统计量
	 * @param user				保存过滤条件的信息实体
	 * @param connection		连接对象
	 * @return						返回统计量
	 * @throws Exception
	 */
	private int size(Message message,Connection connection) throws Exception {
		int result = 0 ;
		PreparedStatement statement = null ;
		ResultSet set = null ;
		
		try{
			String sql = MessageArgument.COUNT_SQL ;	
			String[] Strings =  this.setWhere(message , 0);
			sql = sql + Strings[0];						
			statement = connection.prepareStatement(sql);
			
			if(Strings[1].length() != 0){
				
				Strings = Strings[1].split(",");
				int location = 1;
				
				for(String field : Strings){
					statement.setString(location, BeanUtils.getProperty(message, field));
					location++;
					
				}
				
			}
		
			set = statement.executeQuery();
			
			if( set.next() ){
				result = Integer.valueOf( set.getString(1) );
			}
			
		}catch(Exception e){
			this.logger.error(e);
			throw e;
			
		}finally{
			this.dispose(null,statement,set);	
			
		}

		return result;
	}
	
	
	/**
	 * 
	 * @Description		拼接过滤条件，统计占位符字段
	 * @param user		占位符的值
	 * @param type		0代表查询，1代表更新
	 * @return				返回过滤条件和占位符字段 
	 * 								数组0表示查询过滤条件
	 * 								数组1表示统计占位符字段
	 * 								数组2表示更新过滤条件
	 * @throws Exception
	 */
	private String[] setWhere(Message message, int type) throws Exception{
		StringBuffer where = new StringBuffer();
		StringBuffer field = new StringBuffer();
		String string = new String();
		
		if( message.getMcontent()!= null && !message.getMcontent().equals("") ){
			
			if(type == 1){
				string = string + " message.mcontent=?,";
			}else{
				where.append(" and message.mcontent=? ");
			}
			
			field.append("mcontent,");
		}
		
		if( message.getMdatetime()!= null && !message.getMdatetime().equals("") ){
			
			if(type == 1){
				string = string + " message.mdatetime=?,";
			}else{
				where.append(" and message.mdatetime=? ");
			}
			
			field.append("mdatetime,");
		}
		
		if( message.getUid()!= null && !message.getUid().equals("") ){
			
			if(type == 1){
				string = string + " message.uid=?,";
			}else{
				where.append(" and message.uid=? ");
			}
			
			field.append("uid,");
		}
		
		if(type == 1){
			string = string.substring(0, string.length() - 1);
		}
			
		if( message.getMid()!= null && !message.getMid().equals("") ){
			
			if(type == 1){
				string = string + " where message.mid=? ";
			}else{
				where.append(" and message.mid=? ");
			}

			field.append("mid,");		
		}
		
		String[] Strings = new String[]{where.toString(),field.toString(),string};
		return Strings;
	}

}
